package com.test.mapoffline;

import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteException;
import android.util.Log;

import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.InputStream;

/**
 * 类描述：
 * 需要传入的键：
 * 传入的值类型：
 * 传入的值含义：
 * 是否必传：
 * 作者：郑朝军 on 2017/6/21 14:24
 * 邮箱：1250393285@qq.com
 * 公司：武汉智博创享科技有限公司
 * 修改人：郑朝军 on 2017/6/21 14:24
 * 修改备注：
 */
public class MBTilesFileArchive
{
    private final SQLiteDatabase mDatabase;

    /**
     * 表的属性 (zoom_level INTEGER, tile_column INTEGER, tile_row INTEGER, tile_data BLOB);
     */
    public static final String TABLE_TILES = "cx";

    public static final String COL_TILES_TILE_DATA = "tile_data";

    public static final String TABLE_METADATA = "metadata";

    public static final String COL_VALUE = "value";

    public MBTilesFileArchive(final SQLiteDatabase pDatabase)
    {
        mDatabase = pDatabase;
    }

    public static MBTilesFileArchive getDatabaseFileArchive(final File pFile)
            throws SQLiteException
    {
        return new MBTilesFileArchive(SQLiteDatabase
                .openDatabase(pFile.getAbsolutePath(), null,
                        SQLiteDatabase.NO_LOCALIZED_COLLATORS | SQLiteDatabase.OPEN_READONLY)
        );
    }

    public static MBTilesFileArchive getDatabaseFileArchive(final String path)
            throws SQLiteException
    {
        return new MBTilesFileArchive(SQLiteDatabase
                .openDatabase(path, null,
                        SQLiteDatabase.NO_LOCALIZED_COLLATORS | SQLiteDatabase.OPEN_READONLY)
        );
    }

    public InputStream getInputStream(int x, int y, int level)
    {
        try
        {
            InputStream ret = null;
            final String[] tile = {COL_TILES_TILE_DATA};
            final String[] xyz = {
                    Integer.toString(x),
                    Double.toString(Math.pow(2, level) - y - 1),
                    Integer.toString(level)
            };

            final Cursor cur = mDatabase.query(TABLE_TILES, tile,
                    "tile_column=? and tile_row=? and zoom_level=?", xyz, null, null, null);

            if (cur.getCount() != 0)
            {
                cur.moveToFirst();
                ret = new ByteArrayInputStream(cur.getBlob(0));
            }
            cur.close();
            if (ret != null)
            {
                return ret;
            }
        }
        catch (final Throwable e)
        {
            Log.e(TAG, "Error getting db stream: ", e);
        }

        return null;
    }

    @Override
    public String toString()
    {
        return "MBTiles [mDatabase=" + mDatabase.getPath() + "]";
    }

    private String getStringValue(String key)
    {
        final String[] column = {COL_VALUE};
        final String[] query = {key};

        Cursor c =
                this.mDatabase.query(TABLE_METADATA, column, "name = ?", query, null, null, null);
        try
        {
            c.moveToFirst();
            return c.getString(0);
        }
        catch (Exception e)
        {
            return null;
        }
        finally
        {
            c.close();
        }
    }

    public float getMinZoomLevel()
    {
        String result = getStringValue("minzoom");
        if (result != null)
        {
            return Float.parseFloat(result);
        }
        return 0;
    }

    public float getMaxZoomLevel()
    {
        String result = getStringValue("maxzoom");
        if (result != null)
        {
            return Float.parseFloat(result);
        }
        return 22;
    }

    public String getName()
    {
        return getStringValue("name");
    }

    public String getType()
    {
        return getStringValue("template");
    }

    public String getVersion()
    {
        return getStringValue("version");
    }

    public String getDescription()
    {
        return getStringValue("description");
    }

    public String getAttribution()
    {
        return getStringValue("attribution");
    }

    public void close()
    {
        if (mDatabase != null)
        {
            mDatabase.close();
        }
    }

    private static final String TAG = "MBTilesFileArchive";

}
